package org.example;

import java.lang.reflect.Method;
import java.util.List;

/**
 *  获取Class中方法的参数名
 *  https://stackoverflow.com/questions/2237803/can-i-obtain-method-parameter-name-using-java-reflection
 *
 * 在maven-compiler-plugin中配置 <compilerArgument>-g:none</compilerArgument>
 * javac -g MyController.java 生成的字节码里面有LocalVariableTable,有方法的参数名,反编译可以得到正确的原来的参数名.
 *                                              但是通过反射的话,获取的依旧是arg0,arg1,无法获得原来的参数名
 * javac -g:none MyController.java 生成的字节码里面没有LocalVariableTable,没有方法的参数名,反编译不能得到正确的原来
 *                                               的参数名.通过反射的话,获取的依旧是arg0,arg1,无法获得原来的参数名
 * javac  MyController.java 这种默认方式,同 javac -g:none MyController.java
 *
 *
 * 在java8之前的版本中,无法保留参数名
 * 在java8中, javac 选项可以保留参数名
 * 需要在maven-compiler-plugin中配置 <compilerArgument>-parameters</compilerArgument>
 *   -parameters   Generate metadata for reflection on method parameters
 *                          生成元数据以用于方法参数的反射
 */
public class AppReflectParamName {
    public static void main(String[] args) throws Exception{
//        String clazzName = "org.example.MyClass"; //类名
//        String methodName = "execute";//方法名
        String clazzName = "cn.itcast.usermanage.web.MyController"; //类名
        String methodName = "paraReceive";//方法名

        Class<?> aClass = Class.forName(clazzName);
        Method[] declaredMethods = aClass.getDeclaredMethods();

        for (Method declaredMethod : declaredMethods) {
            if (declaredMethod.getName().equals(methodName)) {
                List<String> parameterNames = MethodsParamUtil.getParameterNames(declaredMethod);
                System.out.println("获取"+clazzName+"类中,"+methodName
                        +"方法的参数名是:"+parameterNames);
                break;
            }
        }
    }
}